package com.example.webshiro.shiro.service.impl;

import cn.hutool.core.collection.CollUtil;
import com.example.webshiro.common.response.ServiceResult;
import com.example.webshiro.server.permission.model.Permission;
import com.example.webshiro.server.permission.service.IPermissionService;
import com.example.webshiro.server.role.model.Role;
import com.example.webshiro.server.role.model.RoleLinkPermission;
import com.example.webshiro.server.role.service.IRoleLinkPermissionService;
import com.example.webshiro.server.role.service.IRoleService;
import com.example.webshiro.server.user.model.User;
import com.example.webshiro.server.user.model.UserLinkRole;
import com.example.webshiro.server.user.service.IUserLinkRoleService;
import com.example.webshiro.server.user.service.IUserService;
import com.example.webshiro.shiro.CurrentUserInfo;
import com.example.webshiro.shiro.service.IAuthService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import javax.persistence.criteria.*;
import java.util.Collection;
import java.util.List;
import java.util.Set;
import java.util.stream.Collectors;

/**
 * @author LuoYu
 * date 2021/2/4
 */
@Service
@Slf4j
public class AuthServiceImpl implements IAuthService {


    @Resource
    private IUserService userService;

    @Resource
    private IUserLinkRoleService userLinkRoleService;

    @Resource
    private IRoleService roleService;

    @Resource
    private IRoleLinkPermissionService roleLinkPermissionService;

    @Resource
    private IPermissionService permissionService;

    @Override
    public ServiceResult<CurrentUserInfo> getUserInfo(String username) {
        log.info("认证授权获取用户信息 ----> 用户名:{}",username);
        Specification<User> specification = (Specification<User>) (root, criteriaQuery, criteriaBuilder) -> {
            //选择查询条件
            Path<Object> name = root.get("username");
            Path<Object> isDeleted = root.get("isDeleted");
            //构造查询条件
            criteriaBuilder.equal(name,username);
            return criteriaBuilder.equal(isDeleted, false);
        };
        //查询用户信息
        User user = userService.getByCondition(specification);
        if(user == null){
            log.error("未找到用户信息 ----> 用户名:{}",username);
            return ServiceResult.error("未找到用户信息");
        }
        CurrentUserInfo userInfo = new CurrentUserInfo();
        Long id = user.getId();
        userInfo.setId(id);
        Specification<UserLinkRole> roleSpecification = (Specification<UserLinkRole>) (root, criteriaQuery, criteriaBuilder) ->{
            //选择查询条件
            Path<Object> userId = root.get("userId");
            return criteriaBuilder.equal(userId,id);
        };
        Collection<UserLinkRole> userLinkRoles = userLinkRoleService.getAllByCondition(roleSpecification);
        if (!CollUtil.isEmpty(userLinkRoles)) {
            Set<Long> roleSet = userLinkRoles.stream().map(UserLinkRole::getRoleId).collect(Collectors.toSet());
            List<Role> roles = roleService.findAll(roleSet);
            userInfo.setRoles(roles);
        }
        return ServiceResult.success(userInfo);
    }

    @Override
    public ServiceResult<List<Permission>> getPermissions(List<Long> roleIds) {
        log.info("获取角色权限");
        if (CollUtil.isEmpty(roleIds)) {
            log.error("角色id集合不能为空....");
            return ServiceResult.error("集合不能为空");
        }
        Specification<RoleLinkPermission> roleSpecification = (Specification<RoleLinkPermission>) (root, criteriaQuery, criteriaBuilder) ->{
            //选择查询条件
            Expression<Long> roleId = root.get("roleId");
            return roleId.in(roleIds);
        };
        List<RoleLinkPermission> roleLinkPermissions = roleLinkPermissionService.getAllByCondition(roleSpecification);
        if(CollUtil.isEmpty(roleLinkPermissions)){
            return ServiceResult.success(CollUtil.newArrayList());
        }
        List<Long> permissionIds = roleLinkPermissions.stream().map(RoleLinkPermission::getPermissionId).collect(Collectors.toList());
        List<Permission> permissions = permissionService.findAll(permissionIds);
        return ServiceResult.success(permissions);
    }
}
